﻿using LightCAD.Core.Elements;
using LightCAD.Core;
using LightCAD.Runtime;
using SkiaSharp;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Xml.Linq;
using netDxf.Entities;
using HarfBuzzSharp;
using System.Net;
using LightCAD.MathLib;
using Avalonia.Controls;

namespace LightCAD.Drawing.Actions
{
    public class DimRotatedAction : ElementAction
    {
        private DimRotatedAction() { }

        public DimRotatedAction(IDocumentEditor docEditor)
            : base(docEditor)
        {
            this.commandCtrl.WriteInfo("命令：DimLinear");
        }


        private static readonly LcCreateMethod[] CreateMethods;

        static DimRotatedAction()
        {
            CreateMethods = new LcCreateMethod[1];
            CreateMethods[0] = new LcCreateMethod()
            {
                Name = "创建线性标注",
                Description = "创建线性标注",
                Steps = new LcCreateStep[]
                                                   {
                                                       new LcCreateStep { Name = "Step0", Options = "指定第一个尺寸界线原点或 <选择对象>:" },
                                                       new LcCreateStep { Name = "Step1", Options = "指定第二条尺寸界线原点:" },
                                                       new LcCreateStep { Name = "Step2", Options = "指定尺寸线位置或\r\n[多行文字(M)/文字(T)/角度(A)/水平(H)/垂直(V)/旋转(R)]:" },
                                                   }
            };
        }

        internal static void Initilize()
        {
            ElementActions.DimRotated = new DimRotatedAction();
            LcDocument.ElementActions.Add(BuiltinElementType.DimRotated, ElementActions.DimRotated);
        }

        private List<Vector2> points;

        private Vector2 firstPoint { get; set; }

        private Vector2 secondPoint { get; set; }
        private Vector2 thirdPoint { get; set; }
        private PointInputer inputer { get; set; }

        private static bool vertical;

        public async void ExecCreate(string[] args = null)
        {
            DocumentManager.CurrentRecorder.BeginAction("DimLinear");

            this.points = new List<Vector2>();
            this.StartCreating();
            this.inputer = new PointInputer(this.docEditor);
            var ElementInputer = new ElementInputer(this.docEditor);
            var curMethod = CreateMethods[0];

        Step0:
            var step0 = curMethod.Steps[0];
            var result0 = await inputer.Execute(step0.Options);
            //var result0 = await inputer.Execute(step0.Options);

            if (inputer.isCancelled)
            {
                this.Cancel();
                goto End;
            }

            // zcb: 增加Res0为空的判定
            if (result0 == null)
            {
                this.Cancel();
                goto End;
            }

            if (result0.ValueX == null)
            {
                if (result0.Option != null)
                {
                    //TODO:AutoCAD画线输入一个数字，是怎么确定点的？
                }
                else
                {
                    goto Step1;
                }
            }

            this.firstPoint = (Vector2)result0.ValueX;

        Step1:
            var step1 = curMethod.Steps[1];
            if (this.points.Count >= 2)
            {
                step1 = curMethod.Steps[2];
            }

            var result1 = await inputer.Execute(step1.Options);
            if (inputer.isCancelled)
            {
                this.Cancel();
                goto End;
            }

            if (result1.ValueX == null)
            {
                if (result1.Option == " ")
                {
                    goto End;
                }
                else if (result1.Option != null)
                {
                    this.commandCtrl.WriteInfo(SR.PointError);
                    goto Step2;
                    //TODO:AutoCAD画线输入一个数字，是怎么确定点的？
                }
                else
                {
                    goto Step2;
                }
            }
            this.secondPoint = (Vector2)result1.ValueX;
        //var lcLine = docRt.Document.CreateObject<DimRotated>(firstPoint, secondPoint);
        //Draw(canvas, lcLine);
        Step2:
            var step2 = curMethod.Steps[2];
            var result2 = await inputer.Execute(step2.Options);
            //var result0 = await inputer.Execute(step0.Options);

            if (inputer.isCancelled)
            {
                this.Cancel();
                goto End;
            }

            // zcb: 增加Res0为空的判定
            if (result2 == null)
            {
                this.Cancel();
                goto End;
            }

            if (result2.ValueX == null)
            {
                if (result2.Option != null)
                {
                    //TODO:AutoCAD画线输入一个数字，是怎么确定点的？
                }
                else
                {
                    goto Step2;
                }
            }

            this.thirdPoint = (Vector2)result2.ValueX;

            if (this.firstPoint.X == this.secondPoint.X)
            {
                vertical = false;
            }
            else if (this.firstPoint.Y == this.secondPoint.Y)
            {
                vertical = true;
            }
            else if ((this.thirdPoint.X > firstPoint.X && this.thirdPoint.X < secondPoint.X) || (this.thirdPoint.X < firstPoint.X && this.thirdPoint.X > secondPoint.X))
            {
                vertical = true;
            }
            else if ((this.thirdPoint.Y > firstPoint.Y && this.thirdPoint.Y < secondPoint.Y) || (this.thirdPoint.Y < firstPoint.Y && this.thirdPoint.Y > secondPoint.Y))
            {
                vertical = false;
            }

            var dimRotated = docRt.Document.CreateObject<DimRotated>(firstPoint, secondPoint, thirdPoint, vertical);

            points.Add(firstPoint);
            points.Add(secondPoint);
            points.Add(thirdPoint);
            firstPoint = secondPoint;

            CreateDimElement(dimRotated);
        End:
            this.inputer = null;
            this.EndCreating();

            if (this.points.Count > 0)
            {
                DocumentManager.CurrentRecorder.EndAction();
            }
            else
            {
                DocumentManager.CurrentRecorder.CancleAction();
            }
        }

        public override void Cancel()
        {
            base.Cancel();
            this.vportRt.SetCreateDrawer(null);
        }
        public void CreateDimElement(LcElement lcElement)
        {
            DimRotated dimRotated = lcElement as DimRotated;
            var doc = this.docRt.Document;

            LcText text = doc.CreateObject<LcText>();
            text.Start = dimRotated.Fifth;
            text.TextStart = dimRotated.Fifth;
            text.Heigh = 500;// this.raduis * 2 / 20 < 1 ? 1 : Math.Round(this.raduis * 2 / 20);
            text.Text = dimRotated.Length.ToString("0.00");
            if (dimRotated.Vertical == "vertical")
                text.Rotate = 180 / Math.PI * (new Vector2(dimRotated.Second.X, dimRotated.Fifth.Y) - dimRotated.Fifth).Angle();
            else
                text.Rotate = 180 / Math.PI * (new Vector2(dimRotated.Third.X, dimRotated.Second.Y) - dimRotated.Fifth).Angle();
            text.Alignment = "左对齐";
            text.Widthfactor = 1;
            text.Tilt = 0;
            dimRotated.Text = text;

            this.docRt.Document.ModelSpace.InsertElement(dimRotated);
        }
        bool isDraw = true;
        //垂直

        public override void DrawAuxLines(SKCanvas canvas)
        {

            if (firstPoint != null && isDraw)
            {
                isDraw = true;
                var mp = this.vportRt.PointerMovedPosition.ToVector2d();
                var wcs_mp = this.vportRt.ConvertScrToWcs(mp);
                DrawAuxLine(canvas, firstPoint, wcs_mp);
            }
            if (secondPoint != null)
            {

                isDraw = false;
                var mp = this.vportRt.PointerMovedPosition.ToVector2d();
                var wcs_mp = this.vportRt.ConvertScrToWcs(mp);
                if (firstPoint.X == secondPoint.X)
                {
                    vertical = false;
                }
                else if (firstPoint.Y == secondPoint.Y)
                {
                    vertical = true;
                }
                else if ((wcs_mp.X > firstPoint.X && wcs_mp.X < secondPoint.X) || (wcs_mp.X < firstPoint.X && wcs_mp.X > secondPoint.X))
                {
                    vertical = true;
                }
                else if ((wcs_mp.Y > firstPoint.Y && wcs_mp.Y < secondPoint.Y) || (wcs_mp.Y < firstPoint.Y && wcs_mp.Y > secondPoint.Y))
                {
                    vertical = false;
                }
                if (vertical)
                {
                    Vector2 newWCS_mp = new Vector2(firstPoint.X, wcs_mp.Y);
                    Vector2 newWCS_mp2 = new Vector2(secondPoint.X, wcs_mp.Y);
                    DrawAuxLine(canvas, firstPoint, newWCS_mp);
                    DrawAuxLine(canvas, secondPoint, newWCS_mp2);
                    DrawAuxLine(canvas, newWCS_mp, newWCS_mp2);
                }
                else
                {
                    Vector2 newWCS_mp = new Vector2(wcs_mp.X, firstPoint.Y);
                    Vector2 newWCS_mp2 = new Vector2(wcs_mp.X, secondPoint.Y);
                    DrawAuxLine(canvas, firstPoint, newWCS_mp);
                    DrawAuxLine(canvas, secondPoint, newWCS_mp2);
                    DrawAuxLine(canvas, newWCS_mp, newWCS_mp2);
                }

            }
        }

        //public override void DrawTemp(SKCanvas canvas)
        //{
        //    for (var i = 1; i < this.points.Count; i++)
        //    {
        //        var pre = this.points[i - 1];
        //        var p = this.points[i];
        //        DrawLine(canvas, pre, p);
        //    }
        //}
        private void DrawAuxLine(SKCanvas canvas, Vector2 p0, Vector2 p1)
        {
            var sk_pre = this.vportRt.ConvertWcsToScr(p0).ToSKPoint();
            var sk_p = this.vportRt.ConvertWcsToScr(p1).ToSKPoint();
            //辅助元素的颜色 
            canvas.DrawLine(sk_pre, sk_p, new SKPaint { Color = this.vportRt.GetAuxColorValue(), IsStroke = true });
            //辅助曲线的颜色，包括辅助长度，辅助角度等
        }

        public override void Draw(SKCanvas canvas, LcElement element, Matrix3 matrix)
        {
            var dimRotated = element as DimRotated;
            var first = matrix.MultiplyPoint(dimRotated.First);
            var second = matrix.MultiplyPoint(dimRotated.Second);
            var fifth = matrix.MultiplyPoint(dimRotated.Fifth);

            Vector2 thirdS = new Vector2();

            Vector2 firstE = new Vector2();
            Vector2 secondE = new Vector2();
            Vector2 thirdE = new Vector2();

            Vector2 ArrowFirst = new Vector2();
            Vector2 ArrowSecond = new Vector2();

            //Vector2d directionF = new Vector2d();
            //directionF = new Vector2d(dimRotated.First.X - dimRotated.Third.X, dimRotated.First.Y - dimRotated.First.Y);
            //double dis = 250;
            //Vector2d lidisptposF = firstE + (new Vector2d(directionF.X * dis, directionF.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionF.X, 2.0) + Math.Pow(directionF.Y, 2.0))));

            //Vector2d directionS = new Vector2d();
            //directionS = new Vector2d(dimRotated.Second.X - dimRotated.Third.X, dimRotated.Second.Y - dimRotated.Second.Y);
            //Vector2d lidisptposS = firstE + (new Vector2d(directionS.X * dis, directionS.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionS.X, 2.0) + Math.Pow(directionS.Y, 2.0))));

            if (string.IsNullOrEmpty(dimRotated.Vertical))
            {

                if (vertical)
                {
                    dimRotated.Vertical = "vertical";
                    Vector2 directionF = new Vector2();
                    directionF = new Vector2(dimRotated.First.X - dimRotated.First.X, dimRotated.First.Y - dimRotated.Third.Y);
                    double dis = 250;
                    Vector2 lidisptposF = firstE + (new Vector2(directionF.X * dis, directionF.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionF.X, 2.0) + Math.Pow(directionF.Y, 2.0))));

                    Vector2 directionS = new Vector2();
                    directionS = new Vector2(dimRotated.Second.X - dimRotated.Second.X, dimRotated.Second.Y - dimRotated.Third.Y);
                    Vector2 lidisptposS = firstE + (new Vector2(directionS.X * dis, directionS.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionS.X, 2.0) + Math.Pow(directionS.Y, 2.0))));


                    if (dimRotated.Fifth.X < dimRotated.First.X && dimRotated.Fifth.X < dimRotated.Second.X)
                        thirdS = matrix.MultiplyPoint(new Vector2(dimRotated.Fifth.X, dimRotated.Third.Y));
                    else
                        thirdS = matrix.MultiplyPoint(new Vector2(dimRotated.First.X, dimRotated.Third.Y));

                    firstE = matrix.MultiplyPoint(new Vector2(dimRotated.First.X - lidisptposF.X, dimRotated.Third.Y - lidisptposF.Y));
                    secondE = matrix.MultiplyPoint(new Vector2(dimRotated.Second.X - lidisptposS.X, dimRotated.Third.Y - lidisptposS.Y));
                    if (dimRotated.Fifth.X > dimRotated.First.X && dimRotated.Fifth.X > dimRotated.Second.X)
                        thirdE = matrix.MultiplyPoint(new Vector2(dimRotated.Fifth.X, dimRotated.Third.Y));
                    else
                        thirdE = matrix.MultiplyPoint(new Vector2(dimRotated.Second.X, dimRotated.Third.Y));

                    ArrowFirst = matrix.MultiplyPoint(new Vector2(dimRotated.First.X, dimRotated.Third.Y));
                    ArrowSecond = matrix.MultiplyPoint(new Vector2(dimRotated.Second.X, dimRotated.Third.Y));
                }
                else
                {
                    dimRotated.Vertical = "horizontal";
                    Vector2 directionF = new Vector2();
                    directionF = new Vector2(dimRotated.First.X - dimRotated.Third.X, dimRotated.First.Y - dimRotated.First.Y);
                    double dis = 250;
                    Vector2 lidisptposF = firstE + (new Vector2(directionF.X * dis, directionF.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionF.X, 2.0) + Math.Pow(directionF.Y, 2.0))));

                    Vector2 directionS = new Vector2();
                    directionS = new Vector2(dimRotated.Second.X - dimRotated.Third.X, dimRotated.Second.Y - dimRotated.Second.Y);
                    Vector2 lidisptposS = firstE + (new Vector2(directionS.X * dis, directionS.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionS.X, 2.0) + Math.Pow(directionS.Y, 2.0))));

                    if (dimRotated.Fifth.Y < dimRotated.First.Y && dimRotated.Fifth.Y < dimRotated.Second.Y)
                        thirdS = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X, dimRotated.Fifth.Y));
                    else
                        thirdS = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X, dimRotated.First.Y));


                    firstE = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X - lidisptposF.X, dimRotated.First.Y - lidisptposF.Y));
                    secondE = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X - lidisptposS.X, dimRotated.Second.Y - lidisptposS.Y));
                    if (dimRotated.Fifth.Y > dimRotated.First.Y && dimRotated.Fifth.Y > dimRotated.Second.Y)
                        thirdE = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X, dimRotated.Fifth.Y));
                    else
                        thirdE = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X, dimRotated.Fifth.Y));
                    ArrowFirst = matrix.MultiplyPoint(new Vector2(dimRotated.First.X, dimRotated.Third.Y));
                    ArrowSecond = matrix.MultiplyPoint(new Vector2(dimRotated.Second.X, dimRotated.Third.Y));
                }
            }
            else
            {
                if (dimRotated.Vertical == "vertical")
                {
                    Vector2 directionF = new Vector2();
                    directionF = new Vector2(dimRotated.First.X - dimRotated.First.X, dimRotated.First.Y - dimRotated.Third.Y);
                    double dis = 250;
                    Vector2 lidisptposF = firstE + (new Vector2(directionF.X * dis, directionF.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionF.X, 2.0) + Math.Pow(directionF.Y, 2.0))));

                    Vector2 directionS = new Vector2();
                    directionS = new Vector2(dimRotated.Second.X - dimRotated.Second.X, dimRotated.Second.Y - dimRotated.Third.Y);
                    Vector2 lidisptposS = firstE + (new Vector2(directionS.X * dis, directionS.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionS.X, 2.0) + Math.Pow(directionS.Y, 2.0))));

                    if (dimRotated.Fifth.X < dimRotated.First.X && dimRotated.Fifth.X < dimRotated.Second.X)
                        thirdS = matrix.MultiplyPoint(new Vector2(dimRotated.Fifth.X, dimRotated.Third.Y));
                    else
                        thirdS = matrix.MultiplyPoint(new Vector2(dimRotated.First.X, dimRotated.Third.Y));

                    firstE = matrix.MultiplyPoint(new Vector2(dimRotated.First.X - lidisptposF.X, dimRotated.Third.Y - lidisptposF.Y));
                    secondE = matrix.MultiplyPoint(new Vector2(dimRotated.Second.X - lidisptposS.X, dimRotated.Third.Y - lidisptposS.Y));
                    if (dimRotated.Fifth.X > dimRotated.First.X && dimRotated.Fifth.X > dimRotated.Second.X)
                        thirdE = matrix.MultiplyPoint(new Vector2(dimRotated.Fifth.X, dimRotated.Third.Y));
                    else
                        thirdE = matrix.MultiplyPoint(new Vector2(dimRotated.Second.X, dimRotated.Third.Y));

                    ArrowFirst = matrix.MultiplyPoint(new Vector2(dimRotated.First.X, dimRotated.Third.Y));
                    ArrowSecond = matrix.MultiplyPoint(new Vector2(dimRotated.Second.X, dimRotated.Third.Y));
                }
                else
                {
                    Vector2 directionF = new Vector2();
                    directionF = new Vector2(dimRotated.First.X - dimRotated.Third.X, dimRotated.First.Y - dimRotated.First.Y);
                    double dis = 250;
                    Vector2 lidisptposF = firstE + (new Vector2(directionF.X * dis, directionF.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionF.X, 2.0) + Math.Pow(directionF.Y, 2.0))));

                    Vector2 directionS = new Vector2();
                    directionS = new Vector2(dimRotated.Second.X - dimRotated.Third.X, dimRotated.Second.Y - dimRotated.Second.Y);
                    Vector2 lidisptposS = firstE + (new Vector2(directionS.X * dis, directionS.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionS.X, 2.0) + Math.Pow(directionS.Y, 2.0))));

                    if (dimRotated.Fifth.Y < dimRotated.First.Y && dimRotated.Fifth.Y < dimRotated.Second.Y)
                        thirdS = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X, dimRotated.Fifth.Y));
                    else
                        thirdS = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X, dimRotated.First.Y));

                    //Vector2d directionF = new Vector2d();
                    //directionF = new Vector2d(dimRotated.First.X - dimRotated.Third.X, dimRotated.First.Y - dimRotated.First.Y);
                    //double dis = 250;
                    //Vector2d lidisptposF = firstE + (new Vector2d(directionF.X * dis, directionF.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionF.X, 2.0) + Math.Pow(directionF.Y, 2.0))));

                    //Vector2d directionS = new Vector2d();
                    //directionS = new Vector2d(dimRotated.Second.X - dimRotated.Third.X, dimRotated.Second.Y - dimRotated.Second.Y);
                    //Vector2d lidisptposS = firstE + (new Vector2d(directionS.X * dis, directionS.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(directionS.X, 2.0) + Math.Pow(directionS.Y, 2.0))));

                    firstE = matrix.MultiplyPoint(lidisptposF);
                    secondE = matrix.MultiplyPoint(lidisptposS);

                    firstE = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X - lidisptposF.X, dimRotated.First.Y - lidisptposF.Y));
                    secondE = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X - lidisptposS.X, dimRotated.Second.Y - lidisptposS.Y));
                    if (dimRotated.Fifth.Y > dimRotated.First.Y && dimRotated.Fifth.Y > dimRotated.Second.Y)
                        thirdE = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X, dimRotated.Fifth.Y));
                    else
                        thirdE = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X, dimRotated.Second.Y));

                    ArrowFirst = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X, dimRotated.First.Y));
                    ArrowSecond = matrix.MultiplyPoint(new Vector2(dimRotated.Third.X, dimRotated.Second.Y));
                }
            }
            var firstStart = this.vportRt.ConvertWcsToScr(first).ToSKPoint();
            var secondStart = this.vportRt.ConvertWcsToScr(second).ToSKPoint();
            var thirdStart = this.vportRt.ConvertWcsToScr(thirdS).ToSKPoint();

            //if (dimRotated.Vertical == null)
            //{

            //    if (vertical)
            //    {
            //        dimRotated.Vertical = "vertical";

            //    }
            //    else
            //    {
            //        dimRotated.Vertical = "horizontal";

            //    }
            //}
            //else
            //{
            //    if (dimRotated.Vertical == "vertical")
            //    {

            //    }
            //    else
            //    {

            //    }
            //}
            var firstEnd = this.vportRt.ConvertWcsToScr(firstE).ToSKPoint();
            var secondEnd = this.vportRt.ConvertWcsToScr(secondE).ToSKPoint();
            var thirdEnd = this.vportRt.ConvertWcsToScr(thirdE).ToSKPoint();
            //文字定位点
            var textPoint = this.vportRt.ConvertWcsToScr(fifth).ToSKPoint();

            //Vector2d direction = new Vector2d(dimRotated.Second.X - dimRotated.First.X, dimRotated.Second.Y - dimRotated.First.Y);
            //double dis = Math.Abs(50000);
            //Vector2d lidisptpos = dim.End + (new Vector2d(direction.X * dis, direction.Y * dis)) / Math.Sqrt(Math.Abs((Math.Pow(direction.X, 2.0) + Math.Pow(direction.Y, 2.0))));
            //var mnewend = matrix.MultiplyPoint(lidisptpos);
            //var newend = this.vportRt.ConvertWcsToScr(mnewend).ToSKPoint();

            var pen = this.GetDrawPen(dimRotated);
            var path = DrawArrow(ArrowFirst, ArrowSecond);
            var path2 = DrawArrow(ArrowSecond, ArrowFirst);
            var eleAction = (dimRotated.Text.RtAction as ElementAction);
            dimRotated.Text.Start = fifth;
            dimRotated.Text.Text = dimRotated.Length.ToString("0.00");
            eleAction.SetViewport(this.vportRt).Draw(canvas, dimRotated.Text, matrix);
            //eleAction.SetViewport(this.vportRt).GetPropertyObservers();
            if (pen == Constants.defaultPen)
            {
                //TODO:这里可以考虑将实线用颜色做KEY，对SKPaint进行缓存
                using (var elePen = new SKPaint { Color = new SKColor(element.GetColorValue()), IsStroke = true })
                {
                    canvas.DrawLine(firstStart, firstEnd, elePen);
                    canvas.DrawLine(secondStart, secondEnd, elePen);
                    canvas.DrawLine(thirdStart, thirdEnd, elePen);
                    //elePen.Color = SKColors.Red;
                    elePen.Style = SKPaintStyle.Fill;
                    elePen.IsAntialias = true;
                    elePen.StrokeWidth = 2;
                    //绘制路径
                    canvas.DrawPath(path, elePen);
                    canvas.DrawPath(path2, elePen);
                    #region 文字

                    #endregion
                    //canvas.DrawText(dimRotated.Length.ToString(), (thirdStart.X + thirdEnd.X) / 2, (thirdStart.Y + thirdEnd.Y) / 2, elePen);
                }
            }
            else
            {
                canvas.DrawLine(firstStart, firstEnd, pen);
                canvas.DrawLine(secondStart, secondEnd, pen);
                canvas.DrawLine(thirdStart, thirdEnd, pen);

                //elePen.Color = SKColors.Red;
                //pen.Style = SKPaintStyle.Fill;
                //pen.IsAntialias = true;
                //pen.StrokeWidth = 2;
                //绘制路径
                canvas.DrawPath(path, pen);
                canvas.DrawPath(path2, pen);

            }

            #region
            //var path = DrawArrow(third, thirdE);
            //var path2 = DrawArrow(thirdE, third);
            //using (var elePen = new SKPaint { Color = new SKColor(element.GetColorValue()), IsStroke = true })
            //{

            //}

            //using (var elePen = new SKPaint { Color = new SKColor(element.GetColorValue()), IsStroke = true })
            //{
            //    //elePen.Color = SKColors.Red;
            //    elePen.Style = SKPaintStyle.Fill;
            //    elePen.IsAntialias = true;
            //    elePen.StrokeWidth = 2;
            //    //绘制路径
            //    canvas.DrawPath(path2, elePen);
            //}
            #endregion
        }

        public override ControlGrip[] GetControlGrips(LcElement element)
        {
            var dimRotated = element as DimRotated; //getHel
            var grips = new List<ControlGrip>();
            var gripFirst = new ControlGrip
            {
                Element = dimRotated,
                Name = "First",
                Position = dimRotated.First
            };
            grips.Add(gripFirst);
            var gripSecond = new ControlGrip
            {
                Element = dimRotated,
                Name = "Second",
                Position = dimRotated.Second
            };
            grips.Add(gripSecond);
            ControlGrip gripThird = new ControlGrip();
            if (dimRotated.Vertical == "vertical")
            {
                gripThird = new ControlGrip
                {
                    Element = dimRotated,
                    Name = "Third",
                    Position = new Vector2(dimRotated.First.X, dimRotated.Third.Y)
                };
            }
            else
            {
                gripThird = new ControlGrip
                {
                    Element = dimRotated,
                    Name = "Third",
                    Position = new Vector2(dimRotated.Third.X, dimRotated.First.Y)
                };
            }
            grips.Add(gripThird);
            ControlGrip gripFourth = new ControlGrip();
            if (dimRotated.Vertical == "vertical")
            {
                gripFourth = new ControlGrip
                {
                    Element = dimRotated,
                    Name = "Fourth",
                    Position = new Vector2(dimRotated.Second.X, dimRotated.Third.Y)
                };
            }
            else
            {
                gripFourth = new ControlGrip
                {
                    Element = dimRotated,
                    Name = "Fourth",
                    Position = new Vector2(dimRotated.Third.X, dimRotated.Second.Y)
                };
            }
            grips.Add(gripFourth);
            ControlGrip gripFifth = new ControlGrip();
            //if (dimRotated.Vertical == "vertical")
            //{
            //    gripFifth = new ControlGrip
            //    {
            //        Element = dimRotated,
            //        Name = "Fifth",
            //        Position = new Vector2d((dimRotated.First.X + dimRotated.Second.X) / 2, dimRotated.Third.Y)
            //    };
            //}
            //else
            //{

            //}
            gripFifth = new ControlGrip
            {
                Element = dimRotated,
                Name = "Fifth",
                Position = dimRotated.Fifth
            };
            grips.Add(gripFifth);
            return grips.ToArray();
        }

        //public override void CreateElement(LcElement element, Matrix3d matrix)
        //{
        //    var line = element as LcLine;
        //    this.vportRt.ActiveElementSet.AddLine(matrix.MultiplyPoint(line.Start), matrix.MultiplyPoint(line.End));
        //}

        //public override void CreateElement(LcElement element, Vector2d basePoint, double scaleFactor)
        //{
        //    var line = element as LcLine;
        //    Matrix3d matrix3 = Matrix3d.Scale(scaleFactor, basePoint);
        //    this.vportRt.ActiveElementSet.AddLine(matrix3.MultiplyPoint(line.Start), matrix3.MultiplyPoint(line.End));
        //}

        //public override void CreateElement(LcElement element, Vector2d basePoint, Vector2d scaleVector)
        //{
        //    var line = element as LcLine;
        //    Matrix3d matrix3 = Matrix3d.Scale(scaleVector, basePoint);
        //    this.vportRt.ActiveElementSet.AddLine(matrix3.MultiplyPoint(line.Start), matrix3.MultiplyPoint(line.End));
        //}

        private string _gripName;

        private Vector2 _position;

        private DimRotated _dimRotated;

        public override void SetDragGrip(LcElement element, string gripName, Vector2 position, bool isEnd)
        {
            var dimRotated = element as DimRotated;
            _dimRotated = dimRotated;
            if (!isEnd)
            {
                _gripName = gripName;
                _position = position;
            }
            else
            {
                if (gripName == "First")
                    dimRotated.Set(first: position);
                else if (gripName == "Second")
                {
                    dimRotated.Set(second: position);
                }
                else if (gripName == "Third" || gripName == "Fourth" || gripName == "Fifth")
                {
                    dimRotated.Set(third: position);
                }
            }
            //  DocumentManager.CurrentRecorder.EndAction();
        }
        public override void DrawDragGrip(SKCanvas canvas)
        {
            if (_dimRotated == null) return;
            if (_dimRotated.Vertical == "vertical")
            {
                var first = this.vportRt.ConvertWcsToScr(_dimRotated.First);
                if (_gripName == "Second")
                    first = this.vportRt.ConvertWcsToScr(_position);

                var second = this.vportRt.ConvertWcsToScr(_dimRotated.Second);
                if (_gripName == "First")
                    second = this.vportRt.ConvertWcsToScr(_position);
                var third = this.vportRt.ConvertWcsToScr(_dimRotated.Third);

                var fifth = this.vportRt.ConvertWcsToScr(new Vector2((first.X + second.X) / 2, third.Y));
                if (_gripName == "Third" || _gripName == "Fourth" || _gripName == "Fifth")
                {
                    fifth = this.vportRt.ConvertWcsToScr(_position);
                    if (_gripName == "Third")
                        canvas.DrawLine(fifth.ToSKPoint(), new Vector2(first.X, third.Y).ToSKPoint(), Constants.draggingPen);
                    if (_gripName == "Fourth")
                        canvas.DrawLine(fifth.ToSKPoint(), new Vector2(second.X, third.Y).ToSKPoint(), Constants.draggingPen);
                    if (_gripName == "Fifth")
                        canvas.DrawLine(fifth.ToSKPoint(), new Vector2(third.X, third.Y).ToSKPoint(), Constants.draggingPen);

                    canvas.DrawLine(first.ToSKPoint(), new Vector2(first.X, fifth.Y).ToSKPoint(), Constants.draggingPen);
                    canvas.DrawLine(second.ToSKPoint(), new Vector2(second.X, fifth.Y).ToSKPoint(), Constants.draggingPen);
                    canvas.DrawLine(new Vector2(first.X, fifth.Y).ToSKPoint(), new Vector2(second.X, fifth.Y).ToSKPoint(), Constants.draggingPen);

                    this.vportRt.DrawText(_position, _dimRotated.Text.TextStart, _dimRotated.Text.Heigh, _dimRotated.Text.Rotate, Math.Abs(_dimRotated.Length).ToString("0.00"), _dimRotated.Text.Tilt,
                    _dimRotated.Text.Typeface, _dimRotated.Text.Widthfactor, _dimRotated.Text.Alignment, new Matrix3(), canvas, Runtime.Constants.draggingPen);
                }
                if (_gripName == "Second" || _gripName == "First")
                {
                    canvas.DrawLine(first.ToSKPoint(), second.ToSKPoint(), Constants.draggingPen);
                    canvas.DrawLine(new Vector2(first.X, third.Y).ToSKPoint(), new Vector2(second.X, third.Y).ToSKPoint(), Constants.draggingPen);
                }
            }
            else
            {
                var first = this.vportRt.ConvertWcsToScr(_dimRotated.First);
                if (_gripName == "Second")
                    first = this.vportRt.ConvertWcsToScr(_position);

                var second = this.vportRt.ConvertWcsToScr(_dimRotated.Second);
                if (_gripName == "First")
                    second = this.vportRt.ConvertWcsToScr(_position);
                var third = this.vportRt.ConvertWcsToScr(_dimRotated.Third);

                var fifth = this.vportRt.ConvertWcsToScr(new Vector2(third.X, (first.Y + second.Y) / 2));
                if (_gripName == "Third" || _gripName == "Fourth" || _gripName == "Fifth")
                {
                    fifth = this.vportRt.ConvertWcsToScr(_position);
                    if (_gripName == "Third")
                        canvas.DrawLine(fifth.ToSKPoint(), new Vector2(third.X, first.Y).ToSKPoint(), Constants.draggingPen);
                    if (_gripName == "Fourth")
                        canvas.DrawLine(fifth.ToSKPoint(), new Vector2(third.X, second.Y).ToSKPoint(), Constants.draggingPen);
                    if (_gripName == "Fifth")
                        canvas.DrawLine(fifth.ToSKPoint(), new Vector2(third.X, (first.Y + second.Y) / 2).ToSKPoint(), Constants.draggingPen);

                    canvas.DrawLine(first.ToSKPoint(), new Vector2(fifth.X, first.Y).ToSKPoint(), Constants.draggingPen);
                    canvas.DrawLine(second.ToSKPoint(), new Vector2(fifth.X, second.Y).ToSKPoint(), Constants.draggingPen);
                    canvas.DrawLine(new Vector2(fifth.X, first.Y).ToSKPoint(), new Vector2(fifth.X, second.Y).ToSKPoint(), Constants.draggingPen);
                    this.vportRt.DrawText(_position, _dimRotated.Text.TextStart, _dimRotated.Text.Heigh, _dimRotated.Text.Rotate, _dimRotated.Length.ToString("0.00"), _dimRotated.Text.Tilt,
                    _dimRotated.Text.Typeface, _dimRotated.Text.Widthfactor, _dimRotated.Text.Alignment, new Matrix3(), canvas, Runtime.Constants.draggingPen);
                }
                if (_gripName == "Second" || _gripName == "First")
                {
                    canvas.DrawLine(first.ToSKPoint(), second.ToSKPoint(), Constants.draggingPen);
                    canvas.DrawLine(new Vector2(third.X, first.Y).ToSKPoint(), new Vector2(third.X, second.Y).ToSKPoint(), Constants.draggingPen);
                }
            }

        }
        private SKPath DrawArrow(Vector2 start, Vector2 end, double extraAngle = 0)
        {
            LcLine lcline = new LcLine();
            lcline.Start = start;
            lcline.End = end;
            var radian = lcline.Angle;

            var startve = new Vector2(lcline.Start.X, lcline.Start.Y);
            var arrowtwove = new Vector2(lcline.Start.X + 100, lcline.Start.Y + 30);
            var arrowendve = new Vector2(lcline.Start.X + 100, lcline.Start.Y - 30);
            var angle = Utils.RadianToDegree(radian) + extraAngle;
            arrowtwove = Vector2.Rotate(arrowtwove, startve, angle);
            arrowendve = Vector2.Rotate(arrowendve, startve, angle);

            var pointone = this.vportRt.ConvertWcsToScr(startve).ToSKPoint();
            var pointtwo = this.vportRt.ConvertWcsToScr(arrowtwove).ToSKPoint();
            var pointthree = this.vportRt.ConvertWcsToScr(arrowendve).ToSKPoint();

            var path = new SKPath();
            path.FillType = SKPathFillType.EvenOdd;
            //外圈 顺时针
            path.MoveTo((float)pointone.X, (float)pointone.Y);    //起点
            path.LineTo((float)pointtwo.X, (float)pointtwo.Y);
            path.LineTo((float)pointthree.X, (float)pointthree.Y);
            path.Close();
            return path;
        }
        public override List<PropertyObserver> GetPropertyObservers()
        {
            var alignment = new string[]
            {
                "左对齐",
                "右对齐",
            };

            return new List<PropertyObserver>()
                       {
                           new PropertyObserver()
                               {
                                    Name = "Text",
                                    DisplayName = "内容",
                                    CategoryName = "Geometry",
                                    CategoryDisplayName = "文字",
                                    Getter = (ele) => (ele as DimRotated).Text.Text,
                                    Setter = (ele, value) =>
                                       {
                                           var lctext = (ele as DimRotated).Text;
                                           string textvalue = value.ToString();
                                           if(textvalue!=""){
                                           //lctext.Set(textvalue: textvalue);
                                           }

                                       }
                               },
                           new PropertyObserver()
                               {
                                    Name = "Alignment",
                                    DisplayName = "对正",
                                    CategoryName = "Geometry",
                                    CategoryDisplayName = "文字",
                                    PropType = PropertyType.Array,
                                    Source=(ele) => alignment,
                                    Getter = (ele) => (ele as DimRotated).Text.Alignment,
                                    Setter = (ele, value) =>
                                       {
                                           var lctext = (ele as DimRotated).Text;
                                           var textAlignment = value.ToString();
                                           lctext.Set(alignment: textAlignment);
                                       }
                               },
                           new PropertyObserver()
                               {
                                    Name = "Height",
                                    DisplayName = "高度",
                                    CategoryName = "Geometry",
                                    CategoryDisplayName = "文字",
                                    Getter = (ele) =>(ele as DimRotated).Text.Heigh,
                                    Setter = (ele, value) =>
                                       {
                                           var lctext = (ele as DimRotated).Text;
                                           var textheight = Convert.ToDouble(value);
                                           lctext.Set(height: textheight);
                                       }
                               },
                            new PropertyObserver()
                               {
                                    Name = "Rotate",
                                    DisplayName = "旋转",
                                    CategoryName = "Geometry",
                                    CategoryDisplayName = "文字",
                                    Getter = (ele) => Math.Round((ele as DimRotated).Text.Rotate),
                                    Setter = (ele, value) =>
                                       {

                                           var lctext = (ele as DimRotated).Text;
                                           var textRotate = Convert.ToDouble(value);

                                           if(textRotate>0){ 
                                               //如果大于360
                                               while (textRotate>360)
                                               {
                                                   textRotate=textRotate-360;

                                               }
                                           }
                                           if(textRotate<0){
                                               while(textRotate<0){
                                                textRotate=textRotate+360;
                                               }

                                           }
                                           if(textRotate==360){
                                            textRotate=0;
                                           }

                                           lctext.Set(rotate: textRotate);
                                       }
                               },
                              new PropertyObserver()
                               {
                                    Name = "Widthfactor",
                                    DisplayName = "宽度因子",
                                    CategoryName = "Geometry",
                                    CategoryDisplayName = "文字",
                                    Getter = (ele) => (ele as DimRotated).Text.Widthfactor,
                                    Setter = (ele, value) =>
                                       {
                                           var lctext = (ele as DimRotated).Text;
                                           var textWidthfactor = Convert.ToDouble(value);
                                           lctext.Set(widthfactor: textWidthfactor);
                                       }
                               },
                                new PropertyObserver()
                               {
                                    Name = "Tilt",
                                    DisplayName = "倾斜",
                                    CategoryName = "Geometry",
                                    CategoryDisplayName = "文字",
                                    Getter = (ele) => (ele as DimRotated).Text.Tilt,
                                    Setter = (ele, value) =>
                                       {
                                           var lctext = (ele as DimRotated).Text;
                                           var textTilt = Convert.ToDouble(value);
                                           lctext.Set(tilt: textTilt);
                                       }
                               },



                       };
        }
    }
}
